package com.wing.productionPlan.controller.admin;

import cn.hutool.core.bean.BeanUtil;
import com.alibaba.nacos.common.utils.CollectionUtils;
import com.alibaba.nacos.common.utils.StringUtils;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.wing.common.enums.Idempotent;
import com.wing.common.utils.JsonResult;
import com.wing.common.utils.PageResult;
import com.wing.productionPlan.enumeration.AuditStatusEnum;
import com.wing.productionPlan.model.entity.*;
import com.wing.productionPlan.model.response.RequirePlanVO;
import com.wing.productionPlan.service.*;
import com.wing.web.annotation.RequestObjectFieldIgnore;
import com.wing.web.excel.DownExcelUtil;
import com.wing.web.excel.ExcelUtil;
import com.wing.web.excel.RequirePlanExcelln;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.InputStream;
import java.util.*;

@Slf4j
@Validated
@Api(value = "Admin-生产管理-需求计划表新", tags = "#/product/requirePlan/requirePlanList")
@RestController("RequirePlanController")
@RequestMapping("productionPlan/admin/requirePlan")
@RequiredArgsConstructor
public class RequirePlanController {

    private final RequirePlanService requirePlanService;

    private final RequirePlanItermService requirePlanItermService;

    private final  RequirePlanIProductService requirePlanIProductService;

    /**
     * 下载产品数据录入excel模板
     */
    @ApiOperation(value = "下载产品数据录入excel模板")
    @GetMapping("/template")
    public void template(HttpServletResponse response, HttpServletRequest request) throws IOException {
        String[] headerArr = {"PlantCode","工厂名称","物料编码","物料描述","采购组织","采购组名称","物料单位",
                "物料类型","计划接收时间","供应商编码","VendorName","三方仓库存","近三个月平均到货","月份","预测需求数"};
        List<String[]> downData = new ArrayList<>();
        DownExcelUtil.createExcelTemplate(response, request, "需求计划导入模板", Arrays.asList(headerArr),downData, null);
    }

    /**
     * 导入excel
     */
    @ApiOperation(value = "导入excel")
    @PostMapping("/importExcel")
    public JsonResult importExcel(HttpServletRequest request, @RequestParam("file") MultipartFile file) {
        if (file.isEmpty()) {
            return JsonResult.fail("上传文件为空！");
        }
        try {
            //获取原始的文件名
            ExcelUtil<RequirePlanExcelln> reader = new ExcelUtil<>();
            InputStream is = file.getInputStream();
            List<RequirePlanExcelln> list = reader.read(is,RequirePlanExcelln.class);

            if (CollectionUtils.isEmpty(list)) {
                return JsonResult.fail("请在表格中添加数据！");
            }
            requirePlanService.importExcel(list);
        } catch (Exception e) {
            //e.printStackTrace();
            log.error("上传文件异常！异常信息:", e);
            return JsonResult.exception("上传文件异常！异常信息:" + e.getMessage());
        }
        return JsonResult.success("上传成功！");
    }


    /**
     * 手动添加
     * @param requirePlan
     * @return
     */
    @ApiOperation(value = "添加需求计划表", notes = "添加")
    @RequestObjectFieldIgnore({"id", "createTime", "remark"})
    @PostMapping("/savePlan")
    @Idempotent(keyPrefix = "requirePlanAdd")
    public JsonResult savePlan(@RequestBody RequirePlan requirePlan) {
        //添加相关校验
        if(StringUtils.isEmpty(requirePlan.getFactoryName())){
            return JsonResult.fail("请完善表格中数据！");
        }
        if(StringUtils.isEmpty(requirePlan.getPlantCode())){
            return JsonResult.fail("请完善表格中数据！");
        }
        if(requirePlan.getRequirePlanItemList().size()<=0){
            return JsonResult.fail("请添加生产物料数据！");
        }
        //todo 相关生产物料添加是否校验

        return  requirePlanService.savePlan(requirePlan);
    }



    @ApiOperation(value = "查询需求计划列表", notes = "搜索列表")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "page", value = "第几页", defaultValue = "1", example = "1", dataType = "Integer", paramType = "query")
            ,@ApiImplicitParam(name = "limit", value = "每页多少条", defaultValue = "10", example = "10", dataType = "Integer", paramType = "query")
            ,@ApiImplicitParam(name = "sort", value="排序字段名", defaultValue = "create_time", example = "create_time", dataType = "String", paramType = "query")
            ,@ApiImplicitParam(name = "order", value="排序规则(asc:正序, desc:倒序)", defaultValue = "asc", example = "asc", dataType = "String", paramType = "query")
    })
    @GetMapping("/list")
    public PageResult<RequirePlanVO> list(
            @RequestParam(defaultValue = "1") Integer page
            ,@RequestParam(defaultValue = "10") Integer limit
            ,@RequestParam(defaultValue = "create_time") String sort
            ,@RequestParam(defaultValue = "asc") String order
            ,String purchaseTissue
            ,String factoryName
            ,String auditStatus 
            ,String startTime
            ,String endTime
    ) {
        Page<RequirePlanVO> pg = new Page<>(page, limit);
        HashMap map = new HashMap();
        map.put("purchaseTissue", purchaseTissue);
        map.put("factoryName", factoryName);
        map.put("auditStatus", auditStatus);
        map.put("startTime", startTime);
        map.put("endTime", endTime);
        Page<RequirePlanVO> list = requirePlanService.pageList4app(pg, map);
        List<RequirePlanVO> records = list.getRecords();
        for (RequirePlanVO record : records) {
            if(StringUtils.isNotEmpty(record.getAuditStatus())){
                record.setAuditStatusText(AuditStatusEnum.getDescriptionByCode(record.getAuditStatus()));
            }
        }
        return new PageResult<>(list.getRecords(), list.getTotal());
    }


    @ApiOperation(value = "查询需求计划详情", notes = "搜索详情")
    @GetMapping("/getPlanDetail")
    public JsonResult getPlanDetail(@RequestParam("id") Long id) {
       RequirePlanVO appById = requirePlanService.get4appById(id);
       if(appById!=null){
           appById.setAuditStatusText(AuditStatusEnum.getDescriptionByCode(appById.getAuditStatus()));
           // 创建 LambdaQueryWrapper
           LambdaQueryWrapper<RequirePlanItem> wrapper = Wrappers.<RequirePlanItem>lambdaQuery()
                   .eq(RequirePlanItem::getPlanId, appById.getId());

           // 使用服务层的 list 方法进行查询
           List<RequirePlanItem> requirePlanItemList = requirePlanItermService.list(wrapper);

           appById.setRequirePlanItemList(requirePlanItemList);
           return JsonResult.success(appById);
       }else{
           return JsonResult.fail("未发现详情数据！");
       }
    }



    @ApiOperation(value = "修改产品明细表", notes = "修改")
    @PutMapping("/updateRequirePlan")
    @Idempotent(keyPrefix = "requirePlanUpdate")
    public JsonResult updateRequirePlan(@RequestBody RequirePlan requirePlan) {
        RequirePlan requirePlan1 = requirePlanService.getById(requirePlan.getId());
        if (requirePlan1 == null) {
            return JsonResult.fail("修改失败！");
        }
        if (requirePlanService.updateById(requirePlan)) {
            if (CollectionUtils.isNotEmpty(requirePlan.getRequirePlanItemList())) {

                QueryWrapper<RequirePlanItem> wrapper = new QueryWrapper<>();
                wrapper.lambda().eq(RequirePlanItem::getPlanId,requirePlan1.getId());
                requirePlanItermService.remove(wrapper);
                requirePlan.getRequirePlanItemList().forEach(pr -> {
                    pr.setPlanId(requirePlan1.getId());
                    pr.setFactoryName(requirePlan1.getFactoryName());
                    pr.setPlantCode(requirePlan1.getPlantCode());
                });
                //保存明细
                requirePlanItermService.saveBatch(requirePlan.getRequirePlanItemList());

                List<RequirePlanProduct> requirePlanProductList=new ArrayList<>();
                requirePlan.getRequirePlanItemList().forEach(pr -> {
                    pr.setPlanId(requirePlan1.getId());
                    //产品需求明细进行更新  有则更新  没有则跳过
                    // 创建 LambdaQueryWrapper
                    LambdaQueryWrapper<RequirePlanProduct> wrapperPlan = Wrappers.<RequirePlanProduct>lambdaQuery()
                            .eq(RequirePlanProduct::getPlantCode, requirePlan1.getPlantCode())
                            .eq(RequirePlanProduct::getMaterialCode, pr.getMaterialCode())
                            .eq(RequirePlanProduct::getReceiveMouthDate, pr.getReceiveMouthDate());
                    RequirePlanProduct requirePlanProduct1 = requirePlanIProductService.getOne(wrapperPlan);
                    if(requirePlanProduct1!=null){
                        Long id = requirePlanProduct1.getId();
                        //TODO copy对应同字段内容
                        BeanUtil.copyProperties(pr, requirePlanProduct1,true);
                        requirePlanProduct1.setFactoryName(requirePlan.getFactoryName());
                        requirePlanProduct1.setPlantCode(requirePlan.getPlantCode());
                        requirePlanProduct1.setId(id);
                        requirePlanIProductService.updateById(requirePlanProduct1);
                    }else{
                        RequirePlanProduct requirePlanProduct=new RequirePlanProduct();
                        //TODO copy对应同字段内容
                        BeanUtil.copyProperties(pr, requirePlanProduct,true);
                        requirePlanProduct.setFactoryName(requirePlan.getFactoryName());
                        requirePlanProduct.setPlantCode(requirePlan.getPlantCode());
                        requirePlanProduct.setMaterialCode(pr.getMaterialCode());
                        requirePlanProductList.add(requirePlanProduct);
                    }
                });

                if(requirePlanProductList.size()>0){
                    requirePlanIProductService.saveBatch(requirePlanProductList);
                }

            }

            return JsonResult.success("修改成功！");
        }
        return JsonResult.fail("修改失败！");
    }




}
